/**
 *  Serponix is an arcade game in focus to multiplayer based on the classic game Snake.
 *  Copyright (C) 2010 - 2011  Daniel Vala
 *
 *  This program is free software: you can redistribute it and/or modify
 *  it under the terms of the GNU General Public License as published by
 *  the Free Software Foundation, either version 3 of the License,
 *  or  any later version.
 *
 *  This program is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *  GNU General Public License for more details.

 *  You should have received a copy of the GNU General Public License
 *  along with this program.  If not, see <http://www.gnu.org/licenses/>.
 *
 *  If you have any question do not hesitate to contact author
 *  on e-mail address: danielvala42@gmail.com
 */
package com.serponix.game;

import java.awt.Color;
import java.awt.Cursor;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Point;
import java.awt.RenderingHints;
import java.awt.Toolkit;
import java.awt.image.BufferedImage;
import java.util.Observable;
import java.util.Observer;
import javax.swing.JPanel;

/**
 * Třída View se stará o zobrazování grafiky na herní ploše.
 * Podle potřeby zapíná efekty jako antialiasing a interpolaci.
 * Vypočítává rozměr plochy dle aktuální velikosti Okna
 * a co nejlépe využije prostor pro herní plochu.
 * @author Daniel Vala
 */
public class View extends JPanel implements Observer {

    private int fps = 0;
    private long lastTime;
    private String lastFPS = "";
    private GameModel model;

    public View(GameModel model) {
        lastTime = System.currentTimeMillis();
        this.model = model;
        this.model.addObserver(this);

        // nastavení pozadí okrajů
        setBackground(Color.GRAY);


    }

    @Override
    public void paintComponent(Graphics g) {
        super.paintComponent(g);
        Graphics2D g2d = (Graphics2D) g;
        double scaleSirka = getWidth() / (double) model.getSirkaProVzhled();
        double scaleVyska = getHeight() / (double) model.getVyskaProVzhled();
        g2d.scale(Math.min(scaleSirka, scaleVyska), Math.min(scaleSirka, scaleVyska));

        // nastavení pozadí herní plochy
        g.setColor(Color.LIGHT_GRAY);
        // vykreslení obdelníku herní plochy
        g.fillRect(0, 0, model.getSirkaProVzhled(), model.getVyskaProVzhled());
        // nastavení antialiasingu a interpolace
        if (model instanceof ModelTron) {
            g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
            g2d.setRenderingHint(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_NEAREST_NEIGHBOR);
        } else {
            g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
            g2d.setRenderingHint(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_BICUBIC);
        }
        model.paint(g);

        // nastavení méně náročné interpolace na kreslení zdí mapy
        g2d.setRenderingHint(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_NEAREST_NEIGHBOR);
        model.paintZdi(g);
    }

    @Override
    public void update(Observable o, Object arg) {
        repaint(0);
    }

    @Override
    public Dimension getMinimumSize() {
        return getMinimumSize();
    }

    @Override
    public Dimension getPreferredSize() {
        return new Dimension(model.getSirkaProVzhled(), model.getVyskaProVzhled());
    }

    private void setFPS() {
        if (System.currentTimeMillis() > lastTime + 5000) {
            float newFps = (float) (this.fps * 1000) / (float) (System.currentTimeMillis() - lastTime);
            this.fps = 0;
            lastTime = System.currentTimeMillis();
            lastFPS = "fps: " + newFps;
        }
        ++fps;
    }

    public void smazKurzor() {
        BufferedImage bi = new BufferedImage(32, 32, BufferedImage.TYPE_INT_ARGB);
        Cursor invisibleCursor = Toolkit.getDefaultToolkit().createCustomCursor(bi, new Point(0, 0), "invisible");
        setCursor(invisibleCursor);
    }

    public void zobrazKurzor() {
        setCursor(new java.awt.Cursor(java.awt.Cursor.DEFAULT_CURSOR));
    }
}
